<?php

declare(strict_types=1);

namespace app\service\system;

use app\model\system\MenuApiModel;
use app\model\system\RoleMenuModel;
use app\model\system\RoleModel;
use owns\auth\UserAuth;
use think\facade\Db;

class RoleService
{
    /**
     * 列表
     * @param array $param
     */
    public function list(array $param)
    {
        $list = RoleModel::custom($param)
            ->order('sort asc')
            ->pages($param)
            ->select();
        return list_fmt($list, RoleModel::custom($param)->count());
    }
    /**
     * 编辑
     * @param array $data 角色信息
     * @param integer $id 角色id
     */
    public function edit(array $data, int $id): bool
    {
        $auth = UserAuth::instance();
        if ($id) {
            $role = RoleModel::find($data['id']);
            if (!$role) {
                tips('无角色信息');
            }
            $role->updated_by = $auth->username();
        } else {
            $role = new RoleModel();
            $role->created_by = $auth->username();
        }
        $role->name = trim($data['name']);
        $role->alias = trim($data['alias']);
        // 角色别名查重
        $this->_aliasRepeat($role->alias, $id);

        $role->status = $data['status'];
        $role->sort = $data['sort'];
        $role->remark = $data['remark'];
        return $role->save();
    }
    /**
     * 角色别名查重
     * @param string $alias 角色别名
     * @param integer $id 角色id
     */
    protected function _aliasRepeat(string $alias, int $id)
    {
        $map = RoleModel::where('alias', $alias);
        if ($id) {
            $map->where('id', '<>', $id);
        }
        if ($map->find()) {
            tips('角色别名重复，请重新设置');
        }
    }
    /**
     * 设置角色权限
     * @param array $data
     * @param integer $id 角色id
     */
    public function permission(array $data, int $id)
    {
        $role = RoleModel::find($id);
        if (!$role) {
            tips('未找到角色信息，权限设置失败');
        }
        $role->data_scope = $data['data_scope'];
        $role->save();

        // 菜单
        $oldMenu = RoleMenuModel::where('role_id', $id)->select()->toArray();
        if ($oldMenu) {
            $oldMenu = array_column($oldMenu, null, 'menu_id');
        }
        $newMenu = [];
        foreach ($data['menu'] as $menu_id) {
            if (isset($oldMenu[$menu_id])) {
                unset($oldMenu[$menu_id]);
            } else {
                $newMenu[] = ['role_id' => $role->id, 'menu_id' => $menu_id];
            }
        }
        if ($newMenu) {
            Db::table('o_system_role_menu')->insertAll($newMenu);
        }
        if ($oldMenu) {
            RoleMenuModel::whereIn('id', array_column($oldMenu, 'id'))->delete();
        }
    }
    /**
     * 角色菜单
     * @param integer $id 角色id
     */
    public static function roleMenuId(int $id)
    {
        return RoleMenuModel::where('role_id', $id)->column('menu_id');
    }
    /**
     * 角色权限验证
     * @param Request $request
     */
    public static function permissionVerify($request): array
    {
        $baseUrl = $request->baseUrl();
        $method = $request->method();
        $api = MenuApiModel::where('api_method', $method)
            ->where('code', str_replace('/', ':', $baseUrl))
            ->find();
        if (!$api) {
            return [];
        }
        $roleMenu = RoleMenuModel::where('menu_id', $api->menu_id)
            ->where('role_id', $request->auth->role_id)
            ->find();
        if (!$roleMenu) {
            tips('无操作权限');
        }
        //记录操作信息
        if ($api->oper_log) {
            $param = $request->param();
            return [
                'username' => $request->auth->username,
                'method' => $method,
                'router' => $baseUrl,
                'service_name' => $api->menu_id,
                'ip' => $request->ip(),
                'ip_location' => '',
                'request_data' => is_array($param) ? json_encode($param) : '',
            ];
        }
    }
}
